package tuling.netty.io.bio;

import java.net.ServerSocket;
import java.net.Socket;

/**
 * @program: rgs-study0project
 * @description: 简单bio 单线程（演示什么叫做阻塞）
 * @author: Mr.Ren
 * @create: 2023-11-19 21:02
 **/
public class SingleBioServer {
    public static void main(String[] args) throws Exception {
        //创建服务端
        final ServerSocket serverSocket = new ServerSocket(9000);
        System.out.println("服务端启动成功等待客户端连接......");
        while (true) {

            //获取客户端
            // TODO 这里是BIO第一个阻塞点，当服务端启动后会在这里阻塞（知道有客户端连接后才会向下进行，此时服务端是部能干其他事情的）
            final Socket socket = serverSocket.accept();
            System.out.println("客户端连接成功......");
            //方式一：单线程版本。存在的问题，一个服务端只能处理一个客户端的连接请求，使用场景及其少。
            //假如我有10万个请求，那这种方式就是不可用的。
//            handler(socket);
            //方式二：多线程版本，每个客户端我都让服务端的一个线程去处理，缺点：线程太多了，没办法控制，那么可以用线程池。最核心问题，还是线程数太多。
            new Thread(new Runnable() {
                public void run() {
                    try {
                        handler(socket);
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                }
            }).start();
        }
    }

    public static void handler(Socket socket) throws Exception {
        byte[] bytes = new byte[1024];
        System.out.println("服务端正在准备读取客户端发送的数据......");
        //TODO 此处为BIO的第二个阻塞，服务端会阻塞到这里等待客户端发送数据
        int read = socket.getInputStream().read(bytes);
        System.out.println("服务端读取完毕......");
        if (read != -1) {
            System.out.println("客户端发送的数据是：" + new String(bytes, 0, read));
        }
        socket.getOutputStream().write("HelloClient".getBytes());
        socket.getOutputStream().flush();
    }
}
